<?php
/**
 * In this file the class '\UF\Drawing\Color' is defined.
 *
 * @category   UniKap-Framework
 * @package    Drawing
 * @subpackage Core
 * @author     Ulf -UniKado- Kadner <ulfikado@gmail.com>
 * @since      2014-04-04 16:17
 * @version    0.1
 */

namespace UF\Drawing
{

    /**
     * This class defines a object to encapsule a color definition.
     *
     * @property int $R The red color value
     * @property int $Red Alias for 'R'
     * @property int $G The green color value
     * @property int $Green Alias for 'G'
     * @property int $B The blue color value
     * @property int $Blue Alias for 'B'
     * @property int $Hex The hexadecimal representation of the current color (Format: <code>#RRGGBB</code>)
     * @property int $Rgb The RGB representation of the current color (<code>array( red, green, blue )</code>)
     * @since    v0.1
     */
    class Color implements \UF\IStringConverter, \UF\IArrayConverter, \UF\IXmlConverter, \UF\IEquatable, \Serializable
    {

        # <editor-fold defaultstate="collapsed" desc="- - - -   P R O T E C T E D   F I E L D S   - - - - - - - - - - - - - - - - - - -">

        /**
         * The current color data as a associative array with the keys <b>red</b>, <b>green</b>, <b>blue</b>,
         * <b>opacity</b>, <b>alpha</b> and <b>hex</b>.
         *
         * @var    array
         * @since  v0.1
         */
        protected $data;

        # </editor-fold>

        # <editor-fold defaultstate="collapsed" desc="- - - >   C O N S T R U C T O R   - - - - - - - - - - - - - - - - - - - - - - - -">

        /**
         * Inits a new instance.
         *
         * @param  string|int|RGB-Array $colorDefinition The color definition (Defaults to '#ffffff' white)
         * @param  int                  $opacity         The color oppacity 0-100 (Defaults to NULL)
         * @since  v0.1
         */
        public function __construct( $colorDefinition = '#ffffff', $opacity = null )
        {
            if ( false === ( $rgb = \UF\Drawing\ColorTool::Color2Rgb( $colorDefinition ) ) ) $rgb = array( 0, 0, 0 );
            $this->data = array( 'red' => $rgb[0], 'green' => $rgb[1], 'blue' => $rgb[2] );
            if ( \is_null( $opacity ) ) $this->data['opacity'] = null;
            elseif ( $opacity <= 0 )    $this->data['opacity'] = 0;
            elseif ( $opacity >= 100 )  $this->data['opacity'] = 100;
            else                        $this->data['opacity'] = $opacity;
            $this->data['hex'] = \UF\Drawing\ColorTool::Rgb2Hex(
                $this->data['red'], $this->data['green'], $this->data['blue'] );
            if ( \is_null( $opacity ) ) $this->data['alpha'] = null;
            elseif ( $this->data['opacity'] == 100 ) $this->data['alpha'] = 0;
            elseif ( $this->data['opacity'] == 0 ) $this->data['alpha'] = 127;
            else $this->data['alpha'] = ( 127 * ( 100 - $this->data['opacity'] ) ) / 100;
        }

        # </editor-fold>

        # <editor-fold defaultstate="collapsed" desc="- - - -   G E T T E R S   - - - - - - - - - - - - - - - - - - - - - - - - - - - -">

        /**
         * Returns the RGB values as an numerically indexed array (3 elements).
         *
         * @return array 0=Red 1=Green 2=Blue
         * @since  v0.1
         */
        public final function getRGB()
        {
            return [ $this->data['red'], $this->data['green'], $this->data['blue'] ];
        }

        /**
         * Returns the red RGB value of the color.
         *
         * @return int
         * @since  v0.1
         */
        public final function getR()
        {
            return $this->data['red'];
        }

        /**
         * Returns the green RGB value of the color.
         *
         * @return int
         * @since  v0.1
         */
        public final function getG()
        {
            return $this->data['green'];
        }

        /**
         * Returns the blue RGB value of the color.
         *
         * @return int
         * @since  v0.1
         */
        public final function getB()
        {
            return $this->data['blue'];
        }

        /**
         * Returns the alpha value of the color. (<code>0=no-opacity</code> - <code>127=full-opacity</code>)
         *
         * @return int
         * @since  v0.1
         */
        public final function getAlpha()
        {
            return \is_null( $this->data['alpha'] ) ? 0 : $this->data['alpha'];
        }

        /**
         * Returns the opacity of the color in percent. (<code>0 - 100</code>)
         *
         * @return int
         * @since  v0.1
         */
        public final function getOpacity()
        {
            return \is_null( $this->data['opacity'] )
                ? 100 : $this->data['opacity'];
        }

        /**
         * Returns the hexadecimal notation of the current color.
         *
         * @return string
         * @since  v0.1
         */
        public final function getHexadecimal()
        {
            return $this->$this->data['hex'];
        }

        /**
         * Overrides the magic getter for handling read access to dynamic fields.
         *
         * @param  string $name The name of the required dynamic field
         * @return mixed
         * @since  v0.1
         */
        public function __get( $name )
        {
            return $this->get( $name );
        }

        /**
         * @ignore
         */
        protected function get( $name )
        {
            switch (strtolower($name))
            {
                case 'r': case 'red':     return $this->getR();
                case 'g': case 'green':   return $this->getG();
                case 'b': case 'blue':    return $this->getB();
                case 'alpha': case 'a':   return $this->getAlpha();
                case 'opacity': case 'o': return $this->getOpacity();
                case 'rgb':               return $this->getRGB();
                case 'rgba':              return $this->getRGBA();
                case 'argb':              return $this->getARGB();
                case 'hex': case 'h': case 'hexadecimal':
                                          return $this->getHexadecimal();
                default:                  return false;
            }
        }

        # </editor-fold>

        # <editor-fold defaultstate="collapsed" desc="- - - -   S E T T E R S   - - - - - - - - - - - - - - - - - - - - - - - - - - - -">

        /**
         * Sets a new Color, defined as a RGB color definition. This means, it can be a string with format
         * <code>rgb(R,G,B)</code> or <code>R,G,B</code> or its a array. If its a arrayit can be numerically indicated
         * with format <code>0=R,1=G,2=B</code> or a associative with the caseless keys <code>r|red</code>,
         * <code>g|green</code>, <code>b|blue</code>.
         *
         * @param  string|array $rgbValue
         * @return boolean
         * @since  v0.1
         */
        public function setRGB( $rgbValue )
        {
            if ( \is_string( $rgbValue ) ) $this->setRGBString( $rgbValue );
            elseif ( \is_array( $rgbValue ) && 2 < \count( $rgbValue ) ) $this->setRGBArray( $rgbValue );
            else return false;
            return true;
        }

        /**
         * Sets a new value for the red element of a RGB color.
         *
         * @param int $redValue The new red RGB value (0-255)
         * @return boolean
         * @since  v0.1
         */
        public function setR( $redValue )
        {
            if ( 0 > $redValue || 255 < $redValue ) return false;
            $this->data['red'] = $redValue;
            $this->data['hex'] = \UF\Drawing\ColorTool::Rgb2Hex(
                $this->data['red'], $this->data['green'], $this->data['blue'] );
            return true;
        }

        /**
         * Sets a new value for the green element of a RGB color.
         *
         * @param int $greenValue The new green RGB value (0-255)
         * @return boolean
         * @since  v0.1
         */
        public function setG( $greenValue )
        {
            if ( 0 > $greenValue || 255 < $greenValue ) return false;
            $this->data['green'] = $greenValue;
            $this->data['hex']   = \UF\Drawing\ColorTool::Rgb2Hex(
                $this->data['red'], $this->data['green'], $this->data['blue'] );
        }

        /**
         * Sets a new value for the blue element of a RGB color.
         *
         * @param int $blueValue The new blue RGB value (0-255)
         * @return boolean
         * @since  v0.1
         */
        public function setB( $blueValue )
        {
            if ( 0 > $blueValue || 255 < $blueValue ) return false;
            $this->data['blue'] = $blueValue;
            $this->data['hex']  = \UF\Drawing\ColorTool::Rgb2Hex(
                $this->data['red'], $this->data['green'], $this->data['blue'] );
        }

        /**
         * Sets a new color from a color defition usable for web cases. It can be a hexadecimal color definition,
         * a netscape color name, a rgb color string, or a rgb color array.
         *
         * @param  string|array $colorDefinition
         * @return boolean
         * @since  v0.1
         */
        public function setWebColor( $colorDefinition )
        {
            if ( false === ( $rgb = \UF\Drawing\ColorTool::Color2Rgb( $colorDefinition ) ) ) return false;
            $this->data['red']     = $rgb[0];
            $this->data['green']   = $rgb[1];
            $this->data['blue']    = $rgb[2];
            $this->data['alpha']   = 0;
            $this->data['opacity'] = 100;
            $this->data['hex']  = \UF\Drawing\ColorTool::Rgb2Hex(
                $this->data['red'], $this->data['green'], $this->data['blue'] );
            return true;
        }

        /**
         * Sets a new alpha blending value. It also changes the opacity value!
         *
         * @param  int|NULL $value The new alpha (<code>0=no-transparency</code> - <code>127=full-transparency</code>)
         * @return boolean
         * @since  v0.1
         */
        public function setAlpha( $value = null )
        {
            if ( \is_null( $value ) )
            {
                $this->data['alpha']   = null;
                $this->data['opacity'] = null;
                return true;
            }
            if ( 0 > $value || 127 < $value ) return false;
            $this->data['alpha'] = $value;
            if ( $this->data['alpha'] == 0 ) $this->data['opacity'] = 100;
            elseif ( $this->data['alpha'] == 127 ) $this->data['opacity'] = 0;
            else $this->data['opacity'] = \intval( \floor( ( $this->data['alpha'] * 100 ) / 127 ) );
            return true;
        }

        /**
         * Sets a new color opacity value. It also changes the alpha value!
         *
         * @param  int|NULL $value The new opacity value in percent (<code>0 - 100</code>)
         * @return boolean
         * @since  v0.1
         */
        public function setOpacity( $value = null )
        {
            if ( \is_null( $value ) )
            {
                $this->data['alpha']   = null;
                $this->data['opacity'] = null;
                return true;
            }
            if ( $value < 0 || $value > 100 ) return false;
            $this->data['opacity'] = $value;
            if ( $this->data['opacity'] == 100 ) $this->data['alpha'] = 0;
            elseif ( $this->data['opacity'] == 0 ) $this->data['alpha'] = 127;
            else $this->data['alpha'] = ( 127 * ( 100 - $this->data['opacity'] ) ) / 100;
            return true;
        }

        /**
         * Overrides the magic setter for handling write access to dynamic fields.
         *
         * @param  string $name The name of the required dynamic field
         * @param  mixed $value The value to set for the field.
         * @since  v0.1
         */
        public function __set( $name, $value )
        {
            $this->set( $name, $value );
        }

        /**
         * @ignore
         */
        protected function set( $name, $value )
        {
            switch ( \strtolower( $name ) )
            {
                case 'rgb':
                    $this->setRGB( $value );
                    break;
                case 'argb':
                    $this->setARGB( $value );
                    break;
                case 'rgba':
                    $this->setRGBA( $value );
                    break;
                case 'r':
                case 'red':
                    $this->setR( $value );
                    break;
                case 'g':
                case 'green':
                    $this->setG( $value );
                    break;
                case 'b':
                case 'blue':
                    $this->setB( $value );
                    break;
                case 'hex':
                case 'hexadecimal':
                case 'value':
                case 'webcolor':
                    $this->setWebColor( $value );
                    break;
                case 'alpha':
                case 'a':
                    $this->setAlpha( $value );
                    break;
                case 'o':
                case 'opacity':
                    $this->setOpacity( $value );
                    break;
            }
        }

        # </editor-fold>

        # <editor-fold defaultstate="collapsed" desc="- - - -   P U B L I C   M E T H O D S   - - - - - - - - - - - - - - - - - - - - -">

        # <editor-fold defaultstate="collapsed" desc="Implement \UF\IStringConverter">

        /**
         * Returns the color universal with hexadecimal format #RRGGBB.
         *
         * @return string
         * @since  v0.1
         */
        public function __toString()
        {
            return $this->data['hex'];
        }

        /**
         * Returns the color universal with hexadecimal format #RRGGBB.
         *
         * @return string
         * @since  v0.1
         */
        public function toString()
        {
            return (string) $this;
        }

        /**
         * Reinits the current instance data from the defined object string (a color definition).
         *
         * @param  string $objectString The color definition string
         * @return boolean
         * @since  v0.1
         */
        public function fromString( $objectString )
        {
            return $this->setWebColor( $objectString );
        }

        # </editor-fold>

        # <editor-fold defaultstate="collapsed" desc="Implement \Serializable">

        /**
         * Returns the serialized instance data.
         *
         * @return string
         * @since  v0.1
         */
        public function serialize()
        {
            return \serialize( (string) $this );
        }

        /**
         * Deserialize the instance data from the serialized instance string.
         *
         * @param string $serialized
         * @since  v0.1
         */
        public function unserialize( $serialized )
        {
            $this->fromString( \unserialize( $serialized ) );
        }

        # </editor-fold>

        # <editor-fold defaultstate="collapsed" desc="Implement \UF\IEquatable">

        /**
         * Checks if the current instance is equal to defined value.
         *
         * If the 2nd parameter is TRUE, $value can only be equal if its a instance of {@see \UF\Drawing\Color}.
         * Otherwise also values are checked, that can be converted to a {@see \UF\Drawing\Color}, with
         * {@see \UF\Drawing\Color::TryParse()}.
         *
         * @param  mixed   $value
         * @param  boolean $strict Allow only values of type {@see \UF\Drawing\Color}? (Defaults to FALSE)
         * @return boolean
         * @since  v0.1
         */
        public function equals( $value, $strict=false )
        {
            if ( \is_null( $value ) ) return false;
            if ( $value instanceof \UF\Drawing\Color ) return $value->data['hex'] == $this->data['hex'];
            if ( $strict ) return false;
            if ( ! \is_string( $value ) && ! \is_array( $value ) ) return false;
            $c = new \UF\Drawing\Color( '#ffffff' );
            if ( \is_string( $value ) ) return $c->fromString( $value );
            return $c->fromArray( $value );
        }

        # </editor-fold>

        # <editor-fold defaultstate="collapsed" desc="Implement \UF\IArrayConverter">

        /**
         * Returns instance data as a associative array with the keys 'r', 'g', 'b', 'opacity', 'alpha' and 'hex'
         *
         * @return array Array with Keys 'r', 'g', 'b', 'opacity', 'alpha' and 'hex'
         * @since  v0.1
         */
        public function toArray()
        {
            return [
                'r'       => $this->data['red'],
                'g'       => $this->data['green'],
                'b'       => $this->data['blue'],
                'opacity' => \is_null( $this->data['opacity'] ) ? 100 : $this->data['opacity'],
                'alpha'   => \is_null( $this->data['alpha']   ) ? 0   : $this->data['alpha'],
                'hex'     => $this->data['hex']
            ];
        }

        /**
         * Reads the data from the defined array and on success the current instance data will be overwritten by
         * the new data.
         *
         * @param  array $objectData The data array
         * @return boolean
         * @since  v0.1
         */
        public function fromArray( array $objectData )
        {
            $oc = \count( $objectData );
            if ( 1 > $oc ) return false;
            if ( \UF\ArrayHelper::IsNumericIndexed( $objectData ) )
            {
                if ( 3 != $oc ) return false;
                if ( !\UF\ArrayHelper::IsIntegerArray( $objectData ) ) return false;
                $this->data['red']     = $objectData[0];
                $this->data['green']   = $objectData[1];
                $this->data['blue']    = $objectData[2];
                $this->data['opacity'] = $this->data['alpha'] = null;
                $this->data['hex']     = \UF\Drawing\ColorTool::Rgb2Hex(
                    $this->data['red'], $this->data['green'], $this->data['blue'] );
                return true;
            }
            if ( isset( $objectData['red'] ) && isset( $objectData['green'] ) && isset( $objectData['blue'] ) )
            {
                $objectData['r'] = $objectData['red'];
                $objectData['g'] = $objectData['green'];
                $objectData['b'] = $objectData['blue'];
            }
            if ( isset( $objectData['r'] ) && isset( $objectData['g'] ) && isset( $objectData['b'] ) )
            {
                if ( !\is_int( $objectData['r'] ) ) $objectData['r'] = \intval( $objectData['r'] );
                if ( !\is_int( $objectData['g'] ) ) $objectData['g'] = \intval( $objectData['g'] );
                if ( !\is_int( $objectData['b'] ) ) $objectData['b'] = \intval( $objectData['b'] );
                if ( 0 > $objectData['r'] || 0 > $objectData['g'] || 0 > $objectData['b'] ||
                     255 < $objectData['r'] || 255 < $objectData['g'] || 255 < $objectData['b'] )
                    return false;
                $this->data['red']     = $objectData['r'];
                $this->data['green']   = $objectData['g'];
                $this->data['blue']    = $objectData['b'];
                if ( isset( $objectData['opacity'] ) && \is_int( $objectData['opacity'] ) )
                    $this->setOpacity( $objectData['opacity'] );
                else $this->setOpacity();
                if ( isset( $objectData['alpha'] ) && \is_int( $objectData['alpha'] ) )
                    $this->setAlpha( $objectData['alpha'] );
                else $this->setAlpha();
                $this->data['hex'] = \UF\Drawing\ColorTool::Rgb2Hex(
                    $this->data['red'], $this->data['green'], $this->data['blue'] );
                return true;
            }
            if ( ! isset( $objectData['hex'] ) ) return false;
            if ( false === ( $rgb = \UF\Drawing\ColorTool::Color2Rgb( $objectData['hex'] ) ) )
                return false;
            $this->data['red']     = $rgb[0];
            $this->data['green']   = $rgb[1];
            $this->data['blue']    = $rgb[2];
            if ( isset( $objectData['opacity'] ) && \is_int( $objectData['opacity'] ) )
                $this->setOpacity( $objectData['opacity'] );
            else $this->setOpacity();
            if ( isset( $objectData['alpha'] ) && \is_int( $objectData['alpha'] ) )
                $this->setAlpha( $objectData['alpha'] );
            else $this->setAlpha();
            $this->data['hex'] = $objectData['hex'];
            return true;
        }

        # </editor-fold>

        # <editor-fold defaultstate="collapsed" desc="Implement \UF\IXmlConverter">

        /**
         * Reads the instance data from defined XML element. For doing right, the xml element must use the
         * attribute <code>value="#RRGGBB"</code> to define the color in hexadecimal notation. Alternating to it,
         * also the 3 attributes <b>r</b>, <b>g</b> and <b>b</b> can be used. Optional the attribute <b>opacity</b>
         * can be used. If its defined (valid value range is 0-100) it will be used.
         *
         * @param  \SimpleXMLElement $xmlElement The XML element that defines the instance data.
         * @return boolean
         * @since  v0.1
         */
        public function readXML( \SimpleXMLElement $xmlElement )
        {
            if ( isset( $xmlElement['value'] ) )
            {
                if ( ! $this->fromString( (string) $xmlElement['value'] ) ) return false;
                if ( !isset( $xmlElement['opacity'] ) ) return true;
                $this->setOpacity( \intval( (string) $xmlElement['opacity'] ) );
                return true;
            }
            if ( ! isset( $xmlElement['r'] ) || ! isset( $xmlElement['g'] ) || ! isset( $xmlElement['b'] ) )
                return false;
            $rgb = [
                'r' => \intval( (string) $xmlElement['r'] ),
                'g' => \intval( (string) $xmlElement['g'] ),
                'b' => \intval( (string) $xmlElement['b'] )
            ];
            if ( isset( $xmlElement['opacity'] ) ) $rgb['opacity'] = \intval( (string) $xmlElement['opacity'] );
            if ( ! $this->fromArray( $rgb ) ) return false;
            return true;
        }

        /**
         * Writes all instancedata to the defined XmlWriter. Its only written the attribute <b>value</b>, that
         * contains the color definition with a hexadecimal color notation. (e.g.: <code>#ff00cc</code>) Optional
         * the attribute <b>opacity</b> is returned id a usable value lower than 100 is defined. (100 is excluded
         * because its the default)
         *
         * @param  \XmlWriter $w           The XmlWriter
         * @param  string     $elementName The Name of the element to create (Defaults to 'Color') If empty, only
         *                                 the attribute is written to the XmlWriter
         * @since  v0.1
         */
        public function writeXML( \XmlWriter $w, $elementName = 'Color' )
        {
            $useElement = ! empty( $elementName );
            if ( $useElement ) $w->startElement( $elementName );
            $w->writeAttribute( 'value', $this->data['hex'] );
            if ( ! empty( $this->data['opacity'] ) && $this->data['opacity'] < 100 )
                $w->writeAttribute( 'opacity', $this->data['opacity'] );
            if ( $useElement ) $w->endElement();
        }

        # </editor-fold>

        /**
         * @since  v0.1
         */
        public function createGdValue()
        {
            if ( \is_null( $this->alpha ) ) return \hexdec(
                \str_pad( \dechex( $this->red ), 2, 0, \STR_PAD_LEFT ) .
                \str_pad( \dechex( $this->green ), 2, 0, \STR_PAD_LEFT ) .
                \str_pad( \dechex( $this->blue ), 2, 0, \STR_PAD_LEFT ) );
            return \bindec(
                \decbin(  $this->alpha  ) .
                \decbin(  \hexdec( \substr($this->hex, 1) )  )
            );
        }

        /**
         * Gets a clone of this instance.
         *
         * @return \UF\Drawing\Color
         * @since  v0.1
         */
        public function __clone()
        {
            $result = new \UF\Drawing\Color();
            $result->data = $this->data;
            return $result;
        }

        # </editor-fold>

        # <editor-fold defaultstate="collapsed" desc="- - - -   P U B L I C   S T A T I C   M E T H O D S   - - - - - - - - - - - - - -">

        /**
         * Transfers a integer value, that represents a color with a included alpha value (see
         * imagecolorallocatealpha()) to a {@see \UF\Drawing\Color} instance.
         *
         * @param  int $gdValueWithAlpha
         * @return \UF\Drawing\Color
         * @since  v0.1
         */
        public static function FromGdValueWithAlpha( $gdValueWithAlpha )
        {
            $a = ( $gdValueWithAlpha >> 24 ) & 0xFF;
            $r = ( $gdValueWithAlpha >> 16 ) & 0xFF;
            $g = ( $gdValueWithAlpha >> 8 )  & 0xFF;
            $b = $gdValueWithAlpha & 0xFF;
            if ( 0 == $a ) $o = 0;
            elseif ( 127 == $a ) $o = 100;
            else $o = \intval( \floor( ( 100 * $a ) / 127 ) );
            return new \UF\Drawing\Color( [$r, $g, $b], $o );
        }

        /**
         *
         * @param  \UF\Drawing\Color|\SimpleXMLElement|string|array $colorDefinition
         * @param  \UF\Drawing\Color &$output
         * @return boolean
         */
        public static function TryParse( $colorDefinition, &$output )
        {
            $output = null;
            if ( \is_null( $colorDefinition ) || \is_resource( $colorDefinition ) ) return false;
            if ( $colorDefinition instanceof \UF\Drawing\Color )
            {
                $output = $colorDefinition;
                return true;
            }
            $c = new \UF\Drawing\Color();
            if ( $colorDefinition instanceof \SimpleXMLElement )
            {
                if ( ! $c->readXML( $colorDefinition ) ) return false;
                $output = $c;
                return true;
            }
            if ( ! \is_string( $colorDefinition ) && ! \is_array( $colorDefinition ) ) return false;
            if ( \is_string( $colorDefinition ) )
            {
                if ( ! $c->fromString( $colorDefinition ) ) return false;
                $output = $c;
                return true;
            }
            if ( ! $c->fromArray( $colorDefinition ) ) return false;
            $output = $c;
            return true;
        }

        # </editor-fold>

        # <editor-fold defaultstate="collapsed" desc="- - - -   P R I V A T E   M E T H O D S   - - - - - - - - - - - - - - - - - - - -">

        /**
         * @since  v0.1
         */
        private function setRGBString( $rgbString )
        {
            $m = null;
            if ( \preg_match( '~^rgb\((\d{1,3}),\s*(\d{1,3}),\s*(\d{1,3})\)$~', $rgbString, $m ) ) {
                $r = \intval( $m[1] );
                $g = \intval( $m[2] );
                $b = \intval( $m[3] ); }
            elseif ( \preg_match('~^(\d{1,3}),\s*(\d{1,3}),\s*(\d{1,3})$~', $rgbString, $m ) ) {
                $r = \intval( $m[1] );
                $g = \intval( $m[2] );
                $b = \intval( $m[3] ); }
            else return false;
            if ( 0 > $r || 255 < $r ) return false;
            if ( 0 > $g || 255 < $g ) return false;
            if ( 0 > $b || 255 < $b ) return false;
            $this->data['red']   = $r;
            $this->data['green'] = $g;
            $this->data['blue']  = $b;
            $this->data['hex'] = \UF\Drawing\ColorTool::Rgb2Hex( $r, $g, $b );
        }
        /**
         * @since  v0.1
         */
        private function setRGBArray( array $rgbValue )
        {
            if ( isset( $rgbValue[0] ) && isset( $rgbValue[1] ) && isset( $rgbValue[2] ) ) {
                $r = \intval( $rgbValue[0] );
                $g = \intval( $rgbValue[1] );
                $b = \intval( $rgbValue[2] ); }
            else
            {
                $rgbValue = \array_change_key_case( $rgbValue, \CASE_LOWER );
                if ( isset( $rgbValue['r'] ) && isset( $rgbValue['g'] ) && isset( $rgbValue['b'] ) ) {
                    $r = \intval( $rgbValue['r'] );
                    $g = \intval( $rgbValue['g'] );
                    $b = \intval( $rgbValue['b'] ); }
                elseif ( isset( $rgbValue['red'] ) && isset( $rgbValue['green'] ) && isset( $rgbValue['blue'] ) ) {
                    $r = \intval( $rgbValue['red'] );
                    $g = \intval( $rgbValue['green'] );
                    $b = \intval( $rgbValue['blue'] ); }
                else return false;
            }
            if ( 0 > $r || 255 < $r ) return false;
            if ( 0 > $g || 255 < $g ) return false;
            if ( 0 > $b || 255 < $b ) return false;
            $this->data['red']   = $r;
            $this->data['green'] = $g;
            $this->data['blue']  = $b;
            $this->data['hex']   = \UF\Drawing\ColorTool::Rgb2Hex( $r, $g, $b );
        }

        # </editor-fold>

    }

}

